home *** CD-ROM | disk | FTP | other *** search
/ HPAVC / HPAVC CD-ROM.iso / ABUSESRC.ZIP / AbuseSrc / imlib / port / aix_orig / sound.c < prev   
C/C++ Source or Header  |  1996-07-25  |  8KB  |  327 lines

  1. /*************************************
  2.   Threaded sound driver system
  3. **************************************/
  4.  
  5. // comminicates with sound sub-system via shared memory
  6.  
  7. #include "macs.hpp"
  8. #include "sound.hpp"
  9. #include "readwav.hpp"
  10. #include "dprint.hpp"
  11. #include "jmalloc.hpp"
  12. #include <sys/types.h>
  13. #include <sys/ipc.h>
  14. #include <sys/shm.h>
  15. #include "timing.hpp"
  16. #include <sys/ipc.h>
  17. #include <sys/shm.h>
  18. #include <signal.h>
  19. #include <unistd.h>
  20.  
  21. enum { SFXCMD_QUIT,
  22.        SFXCMD_REGISTER,
  23.        SFXCMD_UNREGISTER,
  24.        SFXCMD_PLAY
  25.      };
  26.  
  27. #define DIN_NAME  "/tmp/sfxdrv.signal"
  28. #define DOUT_NAME "/tmp/sfxdrv.command"
  29.  
  30. class sfx_handle
  31. {
  32.   public :
  33.   int shm_id;
  34.   sound_effect *me;
  35.   sfx_handle   *next;  
  36.   void         *user_data_pointer;
  37.   void         *shm_data_pointer;
  38.   sfx_handle(sound_effect *Me, sfx_handle *Next, void  *UData, void  *SData, int Shm_id)
  39.   { me=Me;
  40.     next=Next;
  41.     shm_id=Shm_id;
  42.     user_data_pointer=UData;
  43.     shm_data_pointer=SData;
  44.   }
  45. } ;
  46.  
  47. static sfx_handle *sfx_list=NULL;
  48. static ushort last_allocated_sfx_id=0;
  49. static int sfx_driver_out_fd=-1,sfx_driver_in_fd=-1;
  50. static int sdriver_pid=0;
  51.  
  52.  
  53. static void kill_sound_driver()
  54. {
  55.   if (sfx_driver_out_fd>=0)
  56.   {
  57.     uchar cmd=SFXCMD_QUIT;        // failed, tell the driver good-bye
  58.     write(sfx_driver_out_fd,&cmd,1);
  59.     close(sfx_driver_out_fd);
  60.     close(sfx_driver_in_fd);
  61.     sfx_driver_out_fd=-1;
  62.  
  63.     milli_wait(10);
  64.     kill(sdriver_pid,SIGUSR1);
  65.     unlink(DIN_NAME);
  66.     unlink(DOUT_NAME);
  67.   }
  68. }
  69.  
  70.  
  71.  
  72. #ifdef __sgi
  73. static void sfx_clean_up(...)
  74. #else
  75. static void sfx_clean_up(int why)      // on exit unattach all shared memory links
  76. #endif
  77. {  
  78.   while (sfx_list)
  79.   {
  80.     if (sfx_driver_out_fd>=0)
  81.     {
  82.       int fail=0;
  83.       uchar cmd=SFXCMD_UNREGISTER;
  84.       if (write(sfx_driver_out_fd,&cmd,1)!=1)
  85.         fail=1;
  86.       else if (write(sfx_driver_out_fd,&sfx_list->shm_id,
  87.              sizeof(sfx_list->shm_id))!=sizeof(sfx_list->shm_id))
  88.         fail=1;
  89.       if (fail) 
  90.       { kill_sound_driver(); }
  91.     }
  92.  
  93.     shmdt((char *)sfx_list->shm_data_pointer);  // detach the shared memory from us
  94.  
  95.     sfx_handle *last=sfx_list;
  96.     sfx_list=sfx_list->next;
  97.     jfree(last);
  98.   }
  99. }
  100.  
  101.  
  102.  
  103. #define TOTAL_SIGS 29
  104.  
  105. int sigs[TOTAL_SIGS]={SIGHUP,SIGINT,SIGQUIT,SIGILL,SIGTRAP,
  106.               SIGABRT,SIGIOT,SIGBUS,SIGFPE,SIGKILL,
  107.               SIGUSR1,SIGSEGV,SIGUSR2,SIGPIPE,SIGALRM,
  108.               SIGTERM,SIGCHLD,SIGCONT,SIGSTOP,
  109.               SIGTSTP,SIGTTIN,SIGTTOU,SIGIO,
  110.               SIGURG,SIGXCPU,SIGXFSZ,SIGVTALRM,SIGPROF,
  111.               SIGWINCH};
  112.  
  113. #include <errno.h>
  114.  
  115. sound_effect::sound_effect(char *filename)
  116. {
  117.     fprintf(stderr, "(%d) snd [%s]: ", sfx_driver_out_fd, filename);
  118.  
  119.   if (sfx_driver_out_fd>=0)
  120.   {
  121.     long sample_speed;
  122.     void *dat=read_wav(filename,sample_speed,size); 
  123.       fprintf(stderr, "1 ");
  124.  
  125.     int id=shmget(IPC_PRIVATE,size,IPC_CREAT | 0777);
  126.     if (id==-1)
  127.     {
  128.       dprintf("Unable to allocate a shared memory id, please clean up\n");
  129.       jfree(dat);
  130.       data=NULL;
  131.     } else
  132.     {
  133.       void *shm_addr=shmat(id,NULL,0);  // attach as read/write
  134.           fprintf(stderr, "2 ");
  135.       if ((long)shm_addr==-1)                   // if not able to attach
  136.       {
  137.                 dprintf("shmat failed, too many shared memory segements or permission denied\n");
  138.                 if (shmctl(id,IPC_RMID,NULL)!=0)
  139.                     dprintf("shmctl failed, why?\n");
  140.                 jfree(dat);
  141.                 data=NULL;
  142.       } else
  143.       {
  144.                 fprintf(stderr, "3 ");
  145.                 memcpy(shm_addr,dat,size);
  146.                 jfree(dat);
  147.  
  148.                 int fail=0;
  149.                 uchar cmd=SFXCMD_REGISTER;
  150.                 if (write(sfx_driver_out_fd,&cmd,1)==0)
  151.                     fail=1;
  152.                 else if (write(sfx_driver_out_fd,&id,sizeof(id))!=sizeof(id))
  153.                     fail=1;
  154.                 else if (write(sfx_driver_out_fd,&size,sizeof(size))!=sizeof(size))
  155.                     fail=1;
  156.                 else if (read(sfx_driver_in_fd,&cmd,1)!=1)
  157.                     fail=1;
  158.                 else if (cmd!=1)    // did we get an 'OK' back so when can delete the shm ID?
  159.                     fail=1;
  160.  
  161.                 fprintf(stderr, "4 ");
  162.                 if (shmctl(id,IPC_RMID,NULL)!=0)
  163.                     dprintf("shmctl failed, why?\n");
  164.  
  165.                 fprintf(stderr, "5 ");
  166.                 if (fail)
  167.                 {
  168.                     kill_sound_driver();
  169.                     shmdt((char *)shm_addr);
  170.                     data=NULL;
  171.                 } else 
  172.                 {
  173.                     fprintf(stderr, "6 ");
  174.                     sfx_list=new sfx_handle(this,sfx_list,dat,shm_addr,id);    
  175.                     data=(void *)sfx_list;
  176.                 }
  177.       }      
  178.     }
  179.   }
  180.  
  181.     fprintf(stderr, "\n");
  182. }
  183.  
  184.  
  185. sound_effect::~sound_effect()
  186. {
  187.   if (sfx_driver_out_fd>=0 && data)
  188.   { 
  189.     sfx_handle *h=(sfx_handle *)data;
  190.     uchar cmd=SFXCMD_UNREGISTER;
  191.     int fail=0;
  192.     if (write(sfx_driver_out_fd,&cmd,1)!=1)
  193.       fail=1;
  194.     else if (write(sfx_driver_out_fd,&h->shm_id,sizeof(h->shm_id))!=sizeof(h->shm_id))
  195.       fail=1;
  196.  
  197.     if (fail)
  198.     { kill_sound_driver(); }
  199.  
  200.     shmdt((char *)h->shm_data_pointer);
  201.       
  202.   }
  203. }
  204.  
  205.  
  206. void sound_effect::play(int volume, int pitch, int panpot)
  207. {
  208.   if (sfx_driver_out_fd>=0 && data)
  209.   {   
  210.     sfx_handle *h=(sfx_handle *)data;
  211.     uchar cmd=SFXCMD_PLAY;
  212.     int fail=0;
  213.     if (write(sfx_driver_out_fd,&cmd,1)!=1)
  214.       fail=1;
  215.     else if (write(sfx_driver_out_fd,&h->shm_id,sizeof(h->shm_id))!=sizeof(h->shm_id))
  216.       fail=1;
  217.     else if (write(sfx_driver_out_fd,&volume,sizeof(volume))!=sizeof(volume))
  218.        fail=1;
  219.  
  220.     if (fail) 
  221.        kill_sound_driver();
  222.   }
  223. }
  224.  
  225.  
  226. int sound_init(int argc, char **argv) 
  227. {
  228.   int i;
  229.   for (i=1;i<argc;i++)
  230.   {
  231.     if (!strcmp(argv[i],"-nosound"))
  232.     {
  233.       dprintf("sound : disabled with (-nosound)\n");
  234.       sfx_driver_out_fd=-1;
  235.       return 0;
  236.     }
  237.   }
  238.  
  239. #if defined(__linux__)
  240.   FILE *sfx_driver_fp=popen("lnx_sdrv","r");
  241. #elif defined(_AIX)
  242.   FILE *sfx_driver_fp=popen("/usr/bin/run_ums aix_sdrv","r");
  243. #else
  244.   FILE *sfx_driver_fp=popen("sgi_sdrv","r");
  245. #endif
  246.  
  247.   if (!sfx_driver_fp)
  248.   {
  249.     dprintf("Error starting sound effect, could not run sfx driver\n"
  250.         "make sure it is in your path and you execute permission\n");
  251.     sfx_driver_out_fd=-1;
  252.     return 0;
  253.   }
  254.  
  255.   char str[100];
  256.   if (!fgets(str,100,sfx_driver_fp) || !sscanf(str,"%d",&sdriver_pid) || sdriver_pid<0)
  257.   {
  258. //    pclose(sfx_driver_fp);
  259.     dprintf("sound effects driver returned failure, sound effects disabled\n");
  260.  //   pclose(sfx_driver_fp);
  261.     sfx_driver_out_fd=-1;
  262.     return 0;
  263.   } else
  264.   {
  265. //    pclose(sfx_driver_fp);
  266.  
  267.     do
  268.     { milli_wait(50);
  269.     } while (access(DIN_NAME,R_OK)); 
  270.     sfx_driver_in_fd=open(DIN_NAME,O_RDWR);
  271.  
  272.     do
  273.     { milli_wait(50);
  274.     } while (access(DOUT_NAME,W_OK)); 
  275.     fprintf(stderr,"opening %s for writing\n",DOUT_NAME);
  276.     sfx_driver_out_fd=open(DOUT_NAME,O_RDWR);
  277.  
  278.     for (int i=0;i<TOTAL_SIGS;i++)
  279.        signal(sigs[i],sfx_clean_up);
  280.  
  281.     atexit(sound_uninit);
  282.   }
  283.   
  284.   return SFX_INITIALIZED;
  285. }
  286.  
  287.  
  288. void sound_uninit()
  289. {
  290.   if (sfx_driver_out_fd>=0)
  291.   {
  292.     if (sfx_list)
  293.     {
  294. #ifdef __sgi
  295.       sfx_clean_up();
  296. #else
  297.       sfx_clean_up(1);
  298. #endif
  299.     }
  300.    
  301.     uchar cmd;
  302.     cmd=SFXCMD_QUIT;
  303.     write(sfx_driver_out_fd,&cmd,1);   // send quit commmand to the driver
  304.     close(sfx_driver_out_fd);          // close connection
  305.     close(sfx_driver_in_fd);          // close connection
  306.     sfx_driver_out_fd=-1;
  307.     sfx_driver_in_fd=-1;
  308.   }
  309. }
  310.  
  311.  
  312.  
  313.  
  314.  
  315.  
  316. song::song(char *filename) { ; }
  317.  
  318. void song::play(unsigned char volume) { ; }
  319. int song::playing() { return 0; }
  320. void song::set_volume(int vol)  { ; }
  321. void song::stop(long fadeout_time) { ;  }
  322. int playing() { return 0; }
  323. song::~song() { ; }
  324.  
  325.  
  326.  
  327.